package com.sudo.service.admin.service.impl;

import com.sudo.common.utils.JsonUtil;
import com.sudo.dao.admin.entity.SysMemLog;
import com.sudo.dao.admin.entity.SysServerNode;
import com.sudo.dao.admin.mapper.SysMemLogMapper;
import com.sudo.dao.admin.model.vo.SysMemCpuVO;
import com.sudo.service.admin.service.AdminBaseService;
import com.sudo.service.admin.service.SysMemLogService;
import com.sudo.service.admin.service.SysServerNodeService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @author 为道日损 2020-07-03 14:47
 * webSite：https://www.sudo.ren
 */
@Service
public class SysMemLogServiceImpl extends AdminBaseService implements SysMemLogService {

    @Resource
    private SysMemLogMapper sysMemLogMapper;

    @Resource
    private SysServerNodeService sysServerNodeService;

    /**
     * 将所有mem信息存入redis
     * @param sysMemLog 内存实体
     */
    @Override
    public void insertMemLogToRedis(String server, SysMemLog sysMemLog) {
        String data = JsonUtil.objectToJson(sysMemLog);
        setSysCpuMemInfoByRealTime(redisKeys.getMemLogRedisRealTimeKey(server),data);
    }

    /**
     * 将redis中的内存信息落地到mysql
     */
    @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    @Override
    public void insertMemLogFromRedisToMysql(String serverNode) {
        String jsonData = stringRedisUtil.lRightPop(redisKeys.getMemLogRedisKey(serverNode));
        if (StringUtils.isNotBlank(jsonData)) {
            SysMemLog sysMemLog = JsonUtil.jsonToPojo(jsonData, SysMemLog.class);
            sysMemLogMapper.insert(sysMemLog);
        }
    }

    /**
     * 获取内存的实时信息
     * @return list数组
     */
    @Override
    public List<SysMemLog> getMemLogListFromRedis(String serverNode) {
        List<SysMemLog> sysMemLogList = new ArrayList<>();
        List<String> memLogArr = stringRedisUtil.lRange(redisKeys.getMemLogRedisRealTimeKey(serverNode), 0, 0);
        for (String s : memLogArr) {
            SysMemLog sysCpuLog = JsonUtil.jsonToPojo(s, SysMemLog.class);
            sysMemLogList.add(sysCpuLog);
        }
        Collections.reverse(sysMemLogList);
        return sysMemLogList;
    }

    @Override
    public Map<String, Object> getAllCpuMemInfoActualTime(Integer num) {
        Map<String, Object> objectMap = new LinkedHashMap<>();
        List<SysServerNode> children = sysServerNodeService.queryAllServerNodes();
        for (SysServerNode child : children) {
            List<String> memCpuArr = stringRedisUtil.lRange(redisKeys.getMemCpuRedisRealTimeKey(child.getServer()), 0, num);
            List<SysMemCpuVO> collect = memCpuArr.stream().map(s -> JsonUtil.jsonToPojo(s, SysMemCpuVO.class)).collect(Collectors.toList());
            objectMap.put(child.getServer(),collect);
        }
        return objectMap;
    }

    @Override
    public String getCpuMemInfoActualTimeByServer(String server,Integer num) {
        List<String> memCpuList = stringRedisUtil.lRange(redisKeys.getMemCpuRedisRealTimeKey(server), 0, num);
        if (CollectionUtils.isEmpty(memCpuList)) {
            return "";
        }
        return memCpuList.get(0);
    }

}
